package model;

import org.mybeans.dao.DAOException;
import org.mybeans.factory.BeanFactory;
import org.mybeans.factory.BeanFactoryException;
import org.mybeans.factory.BeanTable;
import org.mybeans.factory.DuplicateKeyException;
import org.mybeans.factory.MatchArg;
import org.mybeans.factory.RollbackException;
import org.mybeans.factory.Transaction;

import databeans.MailingListData;
import interfas.MailingListDataInterface;

public class MailingListDataDAO implements MailingListDataInterface {

	private BeanFactory<MailingListData> factory;
	
	public MailingListDataDAO() throws DAOException {
		try {
			BeanTable<MailingListData> table = BeanTable.getInstance(MailingListData.class, "mailinglistdata");
			if (!table.exists())
				table.create("respid", "mlid");
			
			table.setIdleConnectionCleanup(true);
			factory = table.getFactory();
		} catch (BeanFactoryException e) {
			throw new DAOException(e);
		}
	}
	
	public void create(MailingListData mld, MailingListDAO mlDAO, UserDAO userDAO) throws DAOException {
		try {
			// Check for foreign key constraint
			if (userDAO.lookup(mld.getRespid()) == null) {
				throw new DAOException("respid must exist in user table");
			}
			if (mlDAO.lookup(mld.getMlid()) == null) {
				throw new DAOException("mlid must exist in mailinglist table");
			}
			
			Transaction.begin();
			MailingListData dbmld = factory.create(mld.getRespid(), mld.getMlid());
			factory.copyInto(mld, dbmld);
			Transaction.commit();
		} catch (DuplicateKeyException e) {
			throw new DAOException("A mailinglist with respid " + mld.getRespid() + " and mlid " + mld.getMlid() + " already exists");
		} catch (RollbackException e) {
			throw new DAOException(e);
		} finally {
			if (Transaction.isActive())
				Transaction.rollback();
		}
	}

	public MailingListData lookup(String respid, int mlid) throws DAOException {
		try {
			return factory.lookup(respid, mlid);
		} catch (RollbackException e) {
			throw new DAOException(e);
		}
	}
	
	public MailingListData[] getMailingListDataByMlid(int mlid) throws DAOException {
		try {
			return factory.match(MatchArg.equals("mlid", mlid));
		} catch (RollbackException e) {
			throw new DAOException(e);
		}
	}
	
	// Update email
	public void update(MailingListData mld, UserDAO userDAO) throws DAOException {
		try {
			if (userDAO.lookup(mld.getRespid()) == null) {
				throw new DAOException("respid must exist in user table");
			}
			Transaction.begin();
			MailingListData dbmld = lookup(mld.getRespid(), mld.getMlid());
			if (dbmld == null) {
				throw new DAOException("MailingListData with respid " + mld.getRespid() + " and mlid " + mld.getMlid() + " doesn't exist");
			}
			dbmld.setEmail(mld.getEmail());
			Transaction.commit();
		} catch (RollbackException e) {
			throw new DAOException(e);
		} finally {
			if (Transaction.isActive())
				Transaction.rollback();
		}
	}
	
	public void delete(String respid, int mlid) throws DAOException {
		try {
			Transaction.begin();
			MailingListData dbmld = lookup(respid, mlid);
			if (dbmld == null)
				throw new DAOException("MailingListData with respid " + respid + " and mlid " + mlid + " doesn't exist");
			factory.delete(respid, mlid);
			Transaction.commit();
		} catch (RollbackException e) {
			throw new DAOException(e);
		} finally {
			if (Transaction.isActive())
				Transaction.rollback();
		}
	}

	public int size() throws DAOException {
		try {
			return factory.getBeanCount();
		} catch (RollbackException e) {
			throw new DAOException(e);
		}
	}
}
